---
title: Collapsible
description: Using the collapsible machine in your project.
package: "@zag-js/collapsible"
---

A collapsible is a component which expands and collapses a panel.

<Resources pkg="@zag-js/collapsible" />

<Showcase id="Collapsible" />

**Features**

- Can be controlled or uncontrolled
- Works for width and height collapsibles

## Installation

To use the collapsible machine in your project, run the following command in
your command line:

<CodeSnippet id="collapsible/installation.mdx" />

## Usage

First, import the collapsible package into your project

```jsx
import * as collapsible from "@zag-js/collapsible"
```

The collapsible package exports two key functions:

- `machine` — The state machine logic for the collapsible widget.
- `connect` — The function that translates the machine's state to JSX attributes
  and event handlers.

> You'll also need to provide a unique `id` to the `useMachine` hook. This is
> used to ensure that every part has a unique identifier.

Next, import the required hooks and functions for your framework and use the
collapsible machine in your project 🔥

<CodeSnippet id="collapsible/usage.mdx" />

### Setting the initial state

Pass the `defaultOpen` machine context property to the machine function to set
the initial state.

```jsx
const service = useMachine(collapsible.machine, {
  defaultOpen: true,
})
```

### Controlled collapsible

To control the open state programmatically, pass the `open` and `onOpenChange`
properties to the machine function.

<CodeSnippet id="collapsible/controlled.mdx" />

### Listening for changes

When the collapsible state changes, the `onOpenChange` callback is invoked.

```jsx {2-5}
const service = useMachine(collapsible.machine, {
  onOpenChange(details) {
    // details => { open: boolean }
    console.log("collapsible open:", details.open)
  },
})
```

### Disabling the collapsible

Set the `disabled` machine context property to `true` to disable the
collapsible.

```jsx {2}
const service = useMachine(collapsible.machine, {
  disabled: true,
})
```

### Partial collapse (setting minimum dimensions)

Use the `collapsedHeight` or `collapsedWidth` machine context properties to
create a "partially collapsed" state. When collapsed, the content will maintain
the specified minimum dimensions instead of collapsing to `0px`.

```jsx {3}
const service = useMachine(collapsible.machine, {
  // Content shows 100px height when collapsed
  collapsedHeight: "100px",
})
```

This is useful for creating "show more/less" content sections or preview states
where a portion of the content shows even when collapsed.

### Animating the collapsible

Use CSS animations to animate the collapsible when it expands and collapses. The
`--height` and `--width` custom properties are attached to the content part.

```css
@keyframes expand {
  from {
    height: var(--collapsed-height, 0);
  }
  to {
    height: var(--height);
  }
}

@keyframes collapse {
  from {
    height: var(--height);
  }
  to {
    height: var(--collapsed-height, 0);
  }
}

[data-scope="collapsible"][data-part="content"] {
  overflow: hidden;
  max-width: 400px;
}

[data-scope="collapsible"][data-part="content"][data-state="open"] {
  animation: expand 110ms cubic-bezier(0, 0, 0.38, 0.9);
}

[data-scope="collapsible"][data-part="content"][data-state="closed"] {
  animation: collapse 110ms cubic-bezier(0, 0, 0.38, 0.9);
}
```

## Styling guide

Earlier, we mentioned that each collapsible part has a `data-part` attribute
added to them to select and style them in the DOM.

### Open and closed state

When a collapsible is expanded or collapsed, a `data-state` attribute is set on
the root, trigger and content elements. This attribute is removed when it is
closed.

```css
[data-part="root"][data-state="open|closed"] {
  /* styles for the collapsible is open or closed state */
}

[data-part="trigger"][data-state="open|closed"] {
  /* styles for the collapsible is open or closed state */
}

[data-part="content"][data-state="open|closed"] {
  /* styles for the collapsible is open or closed state */
}
```

### Focused state

When a collapsible's trigger is focused, a `data-focus` attribute is set on the
root, trigger and content.

```css
[data-part="root"][data-focus] {
  /* styles for the item's focus state */
}

[data-part="trigger"][data-focus] {
  /* styles for the content's focus state */
}

[data-part="content"][data-focus] {
  /* styles for the content's focus state */
}
```

### Collapse animation

The collapsible content provides `--width`, `--height`, `--collapsed-width`, and
`--collapsed-height` CSS variables that can be used to create smooth animations.
These variables are automatically calculated and updated based on the content's
dimensions.

```css
[data-scope="collapsible"][data-part="content"][data-state="open"] {
  animation: slideDown 200ms ease;
}

[data-scope="collapsible"][data-part="content"][data-state="closed"] {
  animation: slideUp 200ms ease;
}

@keyframes slideDown {
  from {
    opacity: 0.01;
    height: 0;
  }
  to {
    opacity: 1;
    height: var(--height);
  }
}

@keyframes slideUp {
  from {
    opacity: 1;
    height: var(--height);
  }
  to {
    opacity: 0.01;
    height: 0;
  }
}
```

## Methods and Properties

The collapsible's `api` exposes the following methods and properties:

### Machine Context

The collapsible machine exposes the following context properties:

<ContextTable name="collapsible" />

### Machine API

The collapsible `api` exposes the following methods:

<ApiTable name="collapsible" />

### Data Attributes

<DataAttrTable name="collapsible" />

### CSS Variables

<CssVarTable name="collapsible" />

## Accessibility

Adheres to the
[Disclosure WAI-ARIA design pattern](https://www.w3.org/WAI/ARIA/apg/patterns/disclosure).

### Keyboard Interactions

<KeyboardTable name="collapsible" />
